package com.zbkj.service.service.impl;


import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.date.DateTime;
import cn.hutool.core.date.DateUtil;
import cn.hutool.core.util.BooleanUtil;
import cn.hutool.core.util.ObjectUtil;
import cn.hutool.core.util.StrUtil;
import cn.hutool.core.util.URLUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.github.pagehelper.Page;
import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import com.zbkj.common.constants.BalanceRecordConstants;
import com.zbkj.common.constants.Constants;
import com.zbkj.common.constants.PayConstants;
import com.zbkj.common.exception.AppException;
import com.zbkj.common.model.member.PaidMemberCard;
import com.zbkj.common.model.member.PaidMemberCardApply;
import com.zbkj.common.model.member.PaidMemberOrder;
import com.zbkj.common.model.order.Order;
import com.zbkj.common.model.product.Product;
import com.zbkj.common.model.user.User;
import com.zbkj.common.model.user.UserBalanceRecord;
import com.zbkj.common.page.CommonPage;
import com.zbkj.common.request.DividendPaidMemberOrderSearchRequest;
import com.zbkj.common.request.PageParamRequest;
import com.zbkj.common.request.PaidMemberOrderSearchRequest;
import com.zbkj.common.response.*;
import com.zbkj.common.result.MemberResultCode;
import com.zbkj.common.result.UserResultCode;
import com.zbkj.common.utils.CrmebDateUtil;
import com.zbkj.common.utils.CrmebUtil;
import com.zbkj.common.utils.ValidateFormUtil;
import com.zbkj.common.vo.DateLimitUtilVo;
import com.zbkj.service.dao.PaidMemberOrderDao;
import com.zbkj.service.service.*;
import com.zbkj.service.util.BrandUtil;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.support.TransactionTemplate;

import javax.annotation.Resource;
import java.math.BigDecimal;
import java.time.*;
import java.util.*;
import java.util.stream.Collectors;

/**
 * @author hzw
 * @description PaidMemberOrderServiceImpl 接口实现
 * @date 2024-05-10
 */
@Service
public class PaidMemberOrderServiceImpl extends ServiceImpl<PaidMemberOrderDao, PaidMemberOrder> implements PaidMemberOrderService {

    private final Logger logger = LoggerFactory.getLogger(PaidMemberOrderServiceImpl.class);

    @Resource
    private PaidMemberOrderDao dao;
    @Autowired
    private UserService userService;
    @Autowired
    private PaidMemberCardService paidMemberCardService;
    @Autowired
    private TransactionTemplate transactionTemplate;
    @Autowired
    private UserBalanceRecordService userBalanceRecordService;
    @Autowired
    private MarketingActivityService marketingActivityService;
    @Autowired
    private PaidMemberCardApplyService paidMemberCardApplyService;

    /**
     * 付费会员订单分页列表
     */
    @Override
    public PageInfo<PaidMemberOrderResponse> findPlatformPage(PaidMemberOrderSearchRequest request) {
        Map<String, Object> map = new HashMap<>();
        if (StrUtil.isNotBlank(request.getOrderNo())) {
            map.put("orderNo", URLUtil.decode(request.getOrderNo()));
        }
        if (StrUtil.isNotBlank(request.getUserNickname())) {
            map.put("userNickname", URLUtil.decode(request.getUserNickname()));
        }
        if (StrUtil.isNotBlank(request.getPhone())) {
            ValidateFormUtil.isPhoneException(request.getPhone());
            map.put("phone", URLUtil.decode(request.getPhone()));
        }
        if (StrUtil.isNotBlank(request.getCardName())) {
            map.put("cardName", URLUtil.decode(request.getCardName()));
        }
        if (StrUtil.isNotBlank(request.getDateLimit())) {
            DateLimitUtilVo dateLimitVo = CrmebDateUtil.getDateLimit(request.getDateLimit());
            map.put("startTime", dateLimitVo.getStartTime());
            map.put("endTime", dateLimitVo.getEndTime());
        }
        if (StrUtil.isNotBlank(request.getPayType())) {
            map.put("payType", request.getPayType());
        }
        if (ObjectUtil.isNotNull(request.getPayStatus())) {
            if (request.getPayStatus() == 1 || request.getPayStatus() == 0) {
                map.put("payStatus", request.getPayStatus());
            }
        }
        map.put("brandId", BrandUtil.getBrandIdByUrl());
//        logger.error("map = " + map.toString() );
        Page<PaidMemberOrderResponse> page = PageHelper.startPage(request.getPage(), request.getLimit());
        List<PaidMemberOrderResponse> list = dao.findPlatformPage(map);
        list.forEach(e -> e.setUserPhone(CrmebUtil.maskMobile(e.getUserPhone())));
        return CommonPage.copyPageInfo(page, list);
    }

    /**
     * 付费会员订单详情
     */
    @Override
    public PaidMemberOrderInfoResponse platformInfo(String orderNo) {
        PaidMemberOrder order = getByOrderNo(orderNo);
        if (ObjectUtil.isNull(order)) {
            throw new AppException(MemberResultCode.PAID_MEMBER_ORDER_NOT_EXIST);
        }
        if (!order.getPaid()) {
            throw new AppException(MemberResultCode.PAID_MEMBER_ORDER_NOT_EXIST);
        }
        User user = userService.getById(order.getUid());
        if (ObjectUtil.isNull(user)) {
            throw new AppException(UserResultCode.USER_NOT_EXIST);
        }
        PaidMemberOrderInfoResponse response = new PaidMemberOrderInfoResponse();
        BeanUtils.copyProperties(order, response);
        response.setUserNickname(user.getNickname());
        response.setUserPhone(CrmebUtil.maskMobile(user.getPhone()));
        return response;
    }

    /**
     * 付费会员订单详情
     */
    @Override
    public PaidMemberOrderInfoResponse platformInfoById(Integer id) {
        PaidMemberOrder order = getById(id);
        if (ObjectUtil.isNull(order)) {
            throw new AppException(MemberResultCode.PAID_MEMBER_ORDER_NOT_EXIST);
        }
        if (!order.getPaid()) {
            throw new AppException(MemberResultCode.PAID_MEMBER_ORDER_NOT_EXIST);
        }
        User user = userService.getById(order.getUid());
        if (ObjectUtil.isNull(user)) {
            throw new AppException(UserResultCode.USER_NOT_EXIST);
        }
        Integer brandIdByUrl = BrandUtil.getBrandIdByUrl();
        if (brandIdByUrl > 0 && !user.getBrandId().equals(brandIdByUrl)) {
            throw new AppException("权限不足");
        }
        PaidMemberOrderInfoResponse response = new PaidMemberOrderInfoResponse();
        BeanUtils.copyProperties(order, response);
        response.setUserNickname(user.getNickname());
        response.setUserPhone(CrmebUtil.maskMobile(user.getPhone()));
        return response;
    }

    /**
     * 用户是否购买过试用类型会员卡
     */
    @Override
    public Boolean userIsPayTrial(Integer userId) {
        LambdaQueryWrapper<PaidMemberOrder> lqw = Wrappers.lambdaQuery();
        lqw.eq(PaidMemberOrder::getUid, userId);
        lqw.eq(PaidMemberOrder::getPaid, 1);
        lqw.eq(PaidMemberOrder::getType, 0);
        Integer count = dao.selectCount(lqw);
        return count > 0;
    }

    /**
     * 用户是否第一次购买该套餐
     */
    @Override
    public Boolean userIsFirstPay(Integer userId, Integer cardId) {
        LambdaQueryWrapper<PaidMemberOrder> lqw = Wrappers.lambdaQuery();
        lqw.eq(PaidMemberOrder::getUid, userId);
        lqw.eq(PaidMemberOrder::getCardId, cardId);
        lqw.eq(PaidMemberOrder::getPaid, 1);
        Integer count = dao.selectCount(lqw);
        return count > 0;
    }

    /**
     * 获取订单
     *
     * @param outTradeNo 商户系统内部的订单号
     */
    @Override
    public PaidMemberOrder getByOutTradeNo(String outTradeNo) {
        LambdaQueryWrapper<PaidMemberOrder> lqw = Wrappers.lambdaQuery();
        lqw.eq(PaidMemberOrder::getOutTradeNo, outTradeNo);
        lqw.last(" limit 1");
        return dao.selectOne(lqw);
    }
    @Override
    public BigDecimal getUserVipPrice(Integer uid) {
        LambdaQueryWrapper<PaidMemberOrder> lqw = Wrappers.lambdaQuery();
        lqw.eq(PaidMemberOrder::getUid, uid);
        List<PaidMemberOrder> order = dao.selectList(lqw);
        BigDecimal  orderPrice = order.stream().map(PaidMemberOrder::getPrice).reduce(BigDecimal::add).orElse(BigDecimal.ZERO);
        return orderPrice;
    }

    public Integer selectCount(Integer uId,Integer cardId) {
        LambdaQueryWrapper<PaidMemberOrder> lqw = Wrappers.lambdaQuery();
        lqw.eq(PaidMemberOrder::getUid, uId);
        lqw.eq(PaidMemberOrder::getCardId, cardId);
        lqw.eq(PaidMemberOrder::getPaid, true);
        return dao.selectCount(lqw);
    }
    /**
     * 赠送用户余额
     * @param svipOrder 支付订单
     */
    @Override
    public Boolean giveGiftBalance(PaidMemberOrder svipOrder) {
        User user = userService.getById(svipOrder.getUid());
        PaidMemberCard card = paidMemberCardService.getByIdException(svipOrder.getCardId());
        Boolean isFirstChargeGive = card.getIsFirstChargeGive();
        BigDecimal giftBalance = card.getGiftBalance();
        if (giftBalance.compareTo(BigDecimal.ZERO) > 0) {
            // 是否仅首充赠送
            if (isFirstChargeGive) {
                Integer firstChargeOrder = selectCount(user.getId(), svipOrder.getCardId());
                //大于1条，不是首充值
                if (firstChargeOrder > 1) {
                    return false;
                }
            }
            // 余额变动
            userService.updateNowMoney(user.getId(), giftBalance, Constants.OPERATION_TYPE_ADD);
            // 创建记录
            userBalanceRecordService.save(createBalanceRecord(svipOrder, user.getNowMoney()));
        }
        return true;
    }
    /**
     * 支付成功后置处理
     * 延长用户vip时限
     * @param svipOrder 支付订单
     */
    @Override
    public Boolean paySuccessAfter(PaidMemberOrder svipOrder) {
        User user = userService.getById(svipOrder.getUid());
        PaidMemberCard card = paidMemberCardService.getByIdException(svipOrder.getCardId());
        Integer deadlineDay = svipOrder.getDeadlineDay();
        boolean isPermanentPaidMember;
        if (user.getIsPermanentPaidMember()) {
            isPermanentPaidMember = true;
        } else {
            isPermanentPaidMember = svipOrder.getType().equals(2);
        }

        Boolean execute = transactionTemplate.execute(e -> {
            boolean update = false;
            DateTime offsetDay;
            if (user.getIsPaidMember()) {
                offsetDay = DateUtil.offsetDay(DateTime.of(user.getPaidMemberExpirationTime()), deadlineDay);
                svipOrder.setCardExpirationTime(offsetDay);
                update = userService.updateUserPaidMember(user.getId(), true, isPermanentPaidMember, offsetDay, user.getPaidMemberExpirationTime());
            } else {
                offsetDay = DateUtil.offsetDay(DateUtil.date(), deadlineDay);
                svipOrder.setCardExpirationTime(offsetDay);
                update = userService.updateUserPaidMember(user.getId(), true, isPermanentPaidMember, offsetDay, null);
            }
            if (!update) {
                logger.error("svip订单更新用户信息失败，orderNo = {}", svipOrder.getOrderNo());
                e.setRollbackOnly();
                return false;
            }
            Boolean updatePaid = updatePaid(svipOrder.getId(), svipOrder.getOrderNo(), offsetDay);
            if (!updatePaid) {
                logger.error("充值订单更新支付状态失败，orderNo = {}", svipOrder.getOrderNo());
                e.setRollbackOnly();
                return false;
            }
            //返利限制 0-无，1-次，2-天，3-周，4-月
            Integer rebateLimit =  card.getRebateLimit();
            //分几次返利，例如rebateLimit是0，则全部返利一次，rebateLimit是1，分rebateNum次，rebateLimit是2，分rebateNum天，rebateLimit是3，分rebateNum周，rebateLimit是4，分rebateNum月
            Integer rebateNum =  card.getRebateNum();
            //开启消费次数
            Boolean isRebateShareLimit =  card.getIsRebateShareLimit();
            //消费金额次数
            Integer rebateShareLimitNum =  card.getRebateShareLimitNum();
            //会员卡售价
            BigDecimal price = svipOrder.getPrice();
            Boolean status = false;
            if (isRebateShareLimit){
                //消费次数限制
                if (rebateShareLimitNum>0){
                    //查询用户消费次数
                    Integer count = dao.getPayCount(user.getId());
                    if (count>=card.getRebateShareLimitNum()){
                        status = true;
                    }
                }else{
                    status = true;
                }
            }else{
                status = true;
            }

            if (price.compareTo(BigDecimal.ZERO) > 0 && status) {
                // 判断规则如果有返利条件，就要做限制
                if (rebateLimit != null && rebateLimit > 0) {
                    BigDecimal giftBalanceNew = getGiftBalance(card);
                    // 剩余余额
                    BigDecimal remaining = price.subtract(giftBalanceNew);
                    // 余额变动
                    userService.updateNowMoney(user.getId(), giftBalanceNew, Constants.OPERATION_TYPE_ADD);
                    // 创建记录
                    userBalanceRecordService.save(createBalanceRecordNew(svipOrder.getId(), svipOrder.getOrderNo(), user.getNowMoney(), giftBalanceNew, remaining));
                } else {
                    // 余额变动
                    userService.updateNowMoney(user.getId(), price, Constants.OPERATION_TYPE_ADD);
                    // 创建记录
                    userBalanceRecordService.save(createBalanceRecord(svipOrder, user.getNowMoney()));
                }
            }

            return Boolean.TRUE;
        });

        return execute;
    }


    /**
     * 获取用户购买svip订单记录
     *
     * @param userId 用户ID
     */
    @Override
    public List<PaidMemberOrder> findUserSvipOrderRecord(Integer userId) {
        LambdaQueryWrapper<PaidMemberOrder> lqw = Wrappers.lambdaQuery();
        lqw.eq(PaidMemberOrder::getUid, userId);
        lqw.eq(PaidMemberOrder::getPaid, 1);
        lqw.orderByDesc(PaidMemberOrder::getPayTime, PaidMemberOrder::getId);
        return dao.selectList(lqw);
    }

    private UserBalanceRecord createBalanceRecord(PaidMemberOrder svipOrder, BigDecimal nowMoney) {
        UserBalanceRecord record = new UserBalanceRecord();
        record.setUid(svipOrder.getUid());
        record.setLinkId(svipOrder.getOrderNo());
        record.setLinkType(BalanceRecordConstants.BALANCE_RECORD_LINK_TYPE_SVIP);
        record.setType(BalanceRecordConstants.BALANCE_RECORD_TYPE_ADD);
        record.setAmount(svipOrder.getGiftBalance());
        record.setBalance(nowMoney.add(svipOrder.getGiftBalance()));
        record.setRemark(StrUtil.format(BalanceRecordConstants.BALANCE_RECORD_REMARK_PAY_SVIP, svipOrder.getGiftBalance()));
        return record;
    }

    private UserBalanceRecord createBalanceRecordNew(Integer uid, String orderNo, BigDecimal nowMoney, BigDecimal giftBalanceNew, BigDecimal remaining) {
        UserBalanceRecord record = new UserBalanceRecord();
        record.setUid(uid);
        record.setLinkId(orderNo);
        record.setLinkType(BalanceRecordConstants.BALANCE_RECORD_LINK_TYPE_SVIP);
        record.setType(BalanceRecordConstants.BALANCE_RECORD_TYPE_ADD);
        record.setAmount(giftBalanceNew);
        record.setBalance(nowMoney.add(giftBalanceNew));
        record.setRemark(StrUtil.format(BalanceRecordConstants.BALANCE_RECORD_REMARK_PAY_SVIP_SPLIT, giftBalanceNew, remaining));
        return record;
    }

    private Boolean updatePaid(Integer id, String orderNo, Date cardExpirationTime) {
        LambdaUpdateWrapper<PaidMemberOrder> wrapper = Wrappers.lambdaUpdate();
        wrapper.set(PaidMemberOrder::getPaid, 1);
        wrapper.set(PaidMemberOrder::getPayTime, CrmebDateUtil.nowDateTime());
        wrapper.set(PaidMemberOrder::getCardExpirationTime, cardExpirationTime);
        wrapper.eq(PaidMemberOrder::getId, id);
        wrapper.eq(PaidMemberOrder::getOrderNo, orderNo);
        wrapper.eq(PaidMemberOrder::getPaid, 0);
        return update(wrapper);
    }

    @Override
    public PaidMemberOrder getByOrderNo(String orderNo) {
        LambdaQueryWrapper<PaidMemberOrder> lqw = Wrappers.lambdaQuery();
        lqw.eq(PaidMemberOrder::getOrderNo, orderNo);
        return dao.selectOne(lqw);
    }

    /**
     * 获取待上传微信发货管理订单
     */
    @Override
    public List<PaidMemberOrder> findAwaitUploadWechatList() {
        DateTime date = DateUtil.date();
        DateTime offsetMinute = DateUtil.offsetMinute(date, -10);
        LambdaQueryWrapper<PaidMemberOrder> lqw = Wrappers.lambdaQuery();
        lqw.eq(PaidMemberOrder::getPaid, 1);
        lqw.eq(PaidMemberOrder::getIsWechatShipping, 0);
        lqw.eq(PaidMemberOrder::getPayType, PayConstants.PAY_TYPE_WE_CHAT);
        lqw.eq(PaidMemberOrder::getPayChannel, PayConstants.PAY_CHANNEL_WECHAT_MINI);
        lqw.le(PaidMemberOrder::getPayTime, offsetMinute);
        return dao.selectList(lqw);
    }

    @Override
    public PaidMemberOrder findLatestUserSvipOrderRecord(Integer userId) {
        LambdaQueryWrapper<PaidMemberOrder> lqw = Wrappers.lambdaQuery();
        lqw.eq(PaidMemberOrder::getUid, userId);
        lqw.eq(PaidMemberOrder::getPaid, 1);
        lqw.orderByDesc(PaidMemberOrder::getPayTime, PaidMemberOrder::getId);
        lqw.last("limit 1");
        return getOne(lqw);
    }



  /*  private BigDecimal getGiftBalance(PaidMemberCard card) {
        if (card.getRebateNum().equals(1)) {
            return card.getGiftBalance();
        }
        return card.getGiftBalance().divide(new BigDecimal(card.getRebateNum().toString()), 2, BigDecimal.ROUND_HALF_UP);
    }*/
    private BigDecimal getGiftBalance(PaidMemberCard card) {
        if (card.getRebateNum().equals(1)) {
            return card.getPrice();
        }
        return card.getPrice().divide(new BigDecimal(card.getRebateNum().toString()), 2, BigDecimal.ROUND_HALF_UP);
    }

    @Override
    public void giftBalanceTask() {
        List<PaidMemberOrderTaskResponse> cardList = dao.getGiftBalanceList();
        if (CollUtil.isNotEmpty(cardList)) {
            for (PaidMemberOrderTaskResponse paidMemberOrderTaskResponse : cardList) {
                logger.info("会员卡赠送余额任务，订单号：{}/{}", paidMemberOrderTaskResponse.getOrderNo(), paidMemberOrderTaskResponse.getId());
                updateGiftBalance(paidMemberOrderTaskResponse);
            }
        }
    }

    @Override
    public PageInfo<PaidMemberOrderPageDataResponse> getPaidMemberOrderList(DividendPaidMemberOrderSearchRequest request, PageParamRequest pageParamRequest) {
        Page<PaidMemberOrderPageDataResponse> page = PageHelper.startPage(pageParamRequest.getPage(), pageParamRequest.getLimit());
        // 获取分红配置
        DividendConfigVo dividendBaseConfig = marketingActivityService.getDividendBaseConfig();
        if (dividendBaseConfig == null || !BooleanUtil.isTrue(dividendBaseConfig.getStatus()) || CollUtil.isEmpty(dividendBaseConfig.getUserTagList())) {
            return CommonPage.copyPageInfo(page, CollUtil.newArrayList());
        }

        Map<String, Object> map = new HashMap<>();
        if (StrUtil.isNotBlank(request.getOrderNo())) {
            map.put("orderNo", URLUtil.decode(request.getOrderNo()));
        }
        if (StrUtil.isNotBlank(request.getUserNickname())) {
            map.put("userNickname", URLUtil.decode(request.getUserNickname()));
        }
        if (StrUtil.isNotBlank(request.getPhone())) {
            ValidateFormUtil.isPhoneException(request.getPhone());
            map.put("phone", URLUtil.decode(request.getPhone()));
        }
        if (StrUtil.isNotBlank(request.getDateLimit())) {
            DateLimitUtilVo dateLimitVo = CrmebDateUtil.getDateLimit(request.getDateLimit());
            map.put("startTime", dateLimitVo.getStartTime());
            map.put("endTime", dateLimitVo.getEndTime());
        }
        if (request.getUid() != null && request.getUid() > 0) {
            map.put("uid", request.getUid());
        }
        map.put("payStatus", 1);

        if (CollUtil.isNotEmpty(dividendBaseConfig.getSourceList())) {
            List<Integer> ids = dividendBaseConfig.getSourceList().stream().filter(x -> BooleanUtil.isTrue(x.getSelected())).map(DividendConfigSourceVo::getId).collect(Collectors.toList());
            map.put("paidCardIds", CollUtil.join(ids, ","));
        }

        map.put("brandId", BrandUtil.getBrandIdByUrl());
        List<PaidMemberOrderResponse> list = dao.findPlatformPage(map);
        list.forEach(e -> e.setUserPhone(CrmebUtil.maskMobile(e.getUserPhone())));
        List<PaidMemberOrderPageDataResponse> listResponse = new ArrayList<>();
        for (PaidMemberOrderResponse paidMemberOrderResponse : list) {
            PaidMemberOrderPageDataResponse paidMemberOrderPageDataResponse = new PaidMemberOrderPageDataResponse();
            BeanUtils.copyProperties(paidMemberOrderResponse, paidMemberOrderPageDataResponse);
            paidMemberOrderPageDataResponse.setUserPhone(CrmebUtil.maskMobile(paidMemberOrderResponse.getUserPhone()));
            listResponse.add(paidMemberOrderPageDataResponse);
        }
        return CommonPage.copyPageInfo(page, listResponse);
    }

    private void updateGiftBalance(PaidMemberOrderTaskResponse response) {
        switch (response.getRebateLimit()){
            case 1:
                // 次，用户有新的余额消费时，返还金额
                // 获取最新赠送余额记录
                UserBalanceRecord prev = userBalanceRecordService.getPrevPaidMemberConsume(response.getUid(), response.getOrderNo());
                if (prev != null) {
                    // 检查赠送余额后用户是否有新的消费
                    UserBalanceRecord consume = userBalanceRecordService.getNewOrderConsume(response.getUid(), prev.getCreateTime());
                    if (consume != null) {
                        // 有新消费，就赠送余额
                        userGiftBalance(response);
                    }
                }
                break;
            case 2:
                // 天
                // 检查今天是否有赠送过
                LocalDateTime startOfDay = LocalDate.now().atStartOfDay();
                Date date = Date.from(startOfDay.atZone(ZoneId.systemDefault()).toInstant());
                UserBalanceRecord curRecord = userBalanceRecordService.getPaidMemberConsumeByDate(response.getUid(), response.getOrderNo(), date);
                if (curRecord == null) {
                    // 就赠送余额
                    userGiftBalance(response);
                }
                break;
            case 3:
                // 周
                // 检查本周是否有赠送过
                LocalDateTime now = LocalDateTime.now();
                LocalDateTime weekStart = now.with(DayOfWeek.MONDAY).with(LocalTime.MIN);
                LocalDateTime weekEnd = now.with(DayOfWeek.SUNDAY).with(LocalTime.MAX);
                UserBalanceRecord curWeekRecord = userBalanceRecordService.getPaidMemberConsumeByDate(response.getUid(), response.getOrderNo(), weekStart, weekEnd);
                if (curWeekRecord == null) {
                    // 赠送余额
                    userGiftBalance(response);
                }
                break;
            case 4:
                // 月
                // 检查本月是否有赠送过
                LocalDateTime nowMonth = LocalDateTime.now();
                YearMonth currentMonth = YearMonth.from(nowMonth);

                LocalDateTime monthStart = currentMonth.atDay(1).atStartOfDay();
                LocalDateTime monthEnd = currentMonth.atEndOfMonth().atTime(LocalTime.MAX);
                UserBalanceRecord curMonthRecord = userBalanceRecordService.getPaidMemberConsumeByDate(response.getUid(), response.getOrderNo(), monthStart, monthEnd);
                if (curMonthRecord == null) {
                    // 赠送余额
                    userGiftBalance(response);
                }
                break;
        }
    }


    /**
     * 赠送余额-按次
     * @param response
     */
    private void userGiftBalance(PaidMemberOrderTaskResponse response) {
        // 赠送的余额
        BigDecimal giftBalanceNew = response.getGiftBalance().divide(new BigDecimal(response.getRebateNum().toString()), 2, BigDecimal.ROUND_HALF_UP);
        // 检查赠送的余额是否找已完成
        BigDecimal add = giftBalanceNew.add(response.getGiftBalanceComplete());
        if (add.compareTo(response.getGiftBalance()) > 0) {
            // 余额赠送过多，减去精度损失
            giftBalanceNew = response.getGiftBalance().subtract(response.getGiftBalanceComplete());
        }

        if (giftBalanceNew.compareTo(BigDecimal.ZERO) > 0) {
            // 剩余余额
            BigDecimal remaining = response.getGiftBalance().subtract(giftBalanceNew).subtract(response.getGiftBalanceComplete());
            // 余额变动
            User user = userService.getNowMoney(response.getUid());
            userService.updateNowMoney(response.getUid(), giftBalanceNew, Constants.OPERATION_TYPE_ADD);
            // 创建记录
            userBalanceRecordService.save(createBalanceRecordNew(response.getUid(), response.getOrderNo(), user.getNowMoney(), giftBalanceNew, remaining));

            Boolean isFinish = false;
            if (remaining.compareTo(BigDecimal.ZERO) == 0) {
                // 赠送完成
                isFinish = true;
            }
            updateOrderStatus(response.getId(), isFinish, response.getGiftBalanceComplete().add(giftBalanceNew));
        }
    }

    private void updateOrderStatus(Integer id, boolean isFinish, BigDecimal giftBalanceComplete) {
        PaidMemberOrder paidMemberOrder = new PaidMemberOrder();
        paidMemberOrder.setId(id);
        paidMemberOrder.setGiftStatus(isFinish);
        paidMemberOrder.setGiftBalanceComplete(giftBalanceComplete);
        updateById(paidMemberOrder);
    }

    public PaidMemberOrderStatResponse getPaidMemberOrderStatPage(DividendPaidMemberOrderSearchRequest request) {
        PaidMemberOrderStatResponse res = new PaidMemberOrderStatResponse();
        res.setTotalPrice(BigDecimal.ZERO);
        res.setPoolAmount(BigDecimal.ZERO);

        DividendConfigVo dividendBaseConfig = marketingActivityService.getDividendBaseConfig();
        if (dividendBaseConfig != null && BooleanUtil.isTrue(dividendBaseConfig.getStatus()) && CollUtil.isNotEmpty(dividendBaseConfig.getSourceList())) {
            for (DividendConfigSourceVo dividendConfigSourceVo : dividendBaseConfig.getSourceList()) {
                if (BooleanUtil.isTrue(dividendConfigSourceVo.getSelected())) {
                    request.setId(dividendConfigSourceVo.getId());
                    BigDecimal amount = getPaidMemberOrderAmount(request);
                    res.setTotalPrice(res.getTotalPrice().add(amount));
                    BigDecimal divide = amount.multiply(dividendConfigSourceVo.getUseRatio()).divide(new BigDecimal("100"), 2, BigDecimal.ROUND_DOWN);
                    res.setPoolAmount(res.getPoolAmount().add(divide));
                }
            }
        }
        return res;
    }

    @Override
    public PaidMemberOrder getLatestById(Integer userId) {
        LambdaQueryWrapper<PaidMemberOrder> lqw = Wrappers.lambdaQuery();
        lqw.select(PaidMemberOrder::getCardId, PaidMemberOrder::getType, PaidMemberOrder::getCardExpirationTime);
        lqw.eq(PaidMemberOrder::getUid, userId);
        lqw.eq(PaidMemberOrder::getPaid, true);
        lqw.orderByDesc(PaidMemberOrder::getPayTime, PaidMemberOrder::getId);
        lqw.last("limit 1");
        PaidMemberOrder paidMemberOrder = getOne(lqw);
        if(paidMemberOrder != null){
            if(!paidMemberOrder.getType().equals(2)){
                // 获取当前时间
                Date now = new Date();
                if (paidMemberOrder.getCardExpirationTime().before(now)) {
                    // 已过期
                    return null;
                }
            }
        }
        return paidMemberOrder;
    }

    /**
     * 获取用户会员卡折扣
     * @param userId
     * @return
     */
    @Override
    public UserDiscountInfoVo getUserDiscount(Integer userId, Product product) {
        //是否参与各级别会员折扣
        Boolean isPaidDiscount = product.getIsPaidDiscount();
        String discountSvipIds = product.getDiscountSvipIds();
        if (userId == null) {
            userId = userService.getUserId();
        }
        UserDiscountInfoVo res = new UserDiscountInfoVo();
        BigDecimal discount = null;
        if (userId != null && userId > 0) {
            PaidMemberOrder paidMemberOrder = this.getLatestById(userId);
            if (paidMemberOrder != null) {
                PaidMemberCard paidMemberCard = paidMemberCardService.getDiscountInfoById(paidMemberOrder.getCardId());
                if (paidMemberCard != null
                        && BooleanUtil.isTrue(isPaidDiscount)
                        && StrUtil.isNotBlank(discountSvipIds)) {
                    String[] svipIds=  discountSvipIds.split(",");
                    long count = Arrays.stream(svipIds).filter(id -> Integer.parseInt(id) == paidMemberCard.getId()).count();
                    if (count==0 && product.getIsCrossover()!=null && product.getIsCrossover()){
                        //查看是否是跨平台商品，是的话看看有没有关联此用户买的会员
                        List<PaidMemberCardApply>  paidMemberCardApplys = paidMemberCardApplyService.getCardApplys(paidMemberCard.getId());
                        count = paidMemberCardApplys.stream()
                                .filter(apply -> Arrays.stream(svipIds)
                                        .map(Integer::parseInt)
                                        .anyMatch(id -> id.equals(apply.getApplyCardId())))
                                .count();
                    }
                    if (count > 0) {
                        res.setVipPaidName(paidMemberCard.getName());
                        //2025-10-25加 会员id
                        res.setId(paidMemberCard.getId());
                        discount = paidMemberCard.getDiscount();
                    }
                }
            }
        }
        res.setDiscount(discount);
        return res;
    }

    @Override
    public Integer getPayCount(Integer userId) {
        return dao.getPayCount(userId);
    }

    @Override
    public BigDecimal getPaidMemberOrderAmount(DividendPaidMemberOrderSearchRequest request) {
        Map<String, Object> map = new HashMap<>();
        if (StrUtil.isNotBlank(request.getOrderNo())) {
            map.put("orderNo", URLUtil.decode(request.getOrderNo()));
        }
        if (CollUtil.isNotEmpty(request.getIds())) {
            map.put("craidIds", CollUtil.join(request.getIds(), ","));
        }
        if (request.getId() != null && request.getId() > 0) {
            map.put("cardId", request.getId());
        }
        if (StrUtil.isNotBlank(request.getUserNickname())) {
            map.put("userNickname", URLUtil.decode(request.getUserNickname()));
        }
        if (StrUtil.isNotBlank(request.getPhone())) {
            ValidateFormUtil.isPhoneException(request.getPhone());
            map.put("phone", URLUtil.decode(request.getPhone()));
        }
        if (StrUtil.isNotBlank(request.getDateLimit())) {
            DateLimitUtilVo dateLimitVo = CrmebDateUtil.getDateLimit(request.getDateLimit());
            map.put("startTime", dateLimitVo.getStartTime());
            map.put("endTime", dateLimitVo.getEndTime());
        }
        if (request.getUid() != null) {
            map.put("uid", request.getUid());
        }
        map.put("payStatus", 1);
        if (request.getBrandId()!=null){
            map.put("brandId", request.getBrandId());

        }else{
            map.put("brandId", BrandUtil.getBrandIdByUrl());
        }
        PaidMemberOrderStatResponse res = dao.findPlatformStat(map);
        if (res == null) {
            return new BigDecimal(0);
        }
        return res.getTotalPrice();
    }

}

